package Domain;

import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 *
 * @author kenneth
 */
public class DropboxServer implements Runnable {
    
    private final int PORT_NUMBER = 1337;
    private ServerSocket serverSocket;
    private boolean run;
    private ExecutorService threadExecutor;
    private ObservableManager om;
    
    public DropboxServer(ObservableManager om) {
        this.om = om;
    }
    
    public void startServer() {
        om.updateMessage("The server is going to start...");
        om.updateMessage("Trying to open the port...");
        try {
            serverSocket = new ServerSocket(PORT_NUMBER);
            om.updateMessage("Port has been opened");
        } catch(Exception e) {
            om.updateMessage(e.getMessage());
            om.updateMessage("Server stopped");
            return;
        }

        run = true;
        threadExecutor = Executors.newCachedThreadPool();
        while(run) {
            om.updateMessage("Waiting for connection");
            try {
                Socket client = serverSocket.accept();
                om.updateMessage("A new connection has been opened");
                ClientConnection cc = new ClientConnection(client,om);
                threadExecutor.execute(cc);
                
            } catch (IOException ex) {
                if(run == true) {
                    om.updateMessage("Failed to initialize a connection");
                }
            }
        }
    }
    
    public void stopServer() {
        threadExecutor.shutdownNow();
        om.updateMessage("Client connections have shutdown");
        om.updateMessage("Trying to close the port");
        try {
            serverSocket.close();
            run = false;
        } catch (IOException ex) {
            om.updateMessage("Failed to close the port");
            return;
        }
        om.updateMessage("Port closed");
        om.updateMessage("Server stopped");
    }

    @Override
    public void run() {
        this.startServer();
    }
    
    public boolean isRunning() {
        return run;
    }
    
}
